using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Forms;
using System.Threading;

namespace Ltf.MonitorLizard.Controllers
{
	public class ListController
	{
		private ListView listView;

		public event EventHandler AfterMultiSelection;

		public ListController(ListView listView, bool isSelectionContiguous, bool raiseAfterMultiSelect)
		{
			this.listView = listView;
			this.isSelectionContiguous = isSelectionContiguous;
			if (raiseAfterMultiSelect)
				listView.SelectedIndexChanged += new EventHandler(listView_SelectedIndexChanged);
			
		}


		bool isSelfChange = false;
		Thread t = null;
		void listView_SelectedIndexChanged(object sender, EventArgs e)
		{

			ThreadStart ts = new ThreadStart(QueueSelectionChange);
			if (t != null)
				t.Abort();

			t = new Thread(ts);
			t.Start();
		}

		private delegate void SelectionChange();

		void QueueSelectionChange()
		{
			Thread.Sleep(100);
			SelectionChange sc = ProcessSelectionChange;
			listView.Invoke(sc);
			t = null;
		}

		void ProcessSelectionChange()
		{

			if (!isSelfChange)
				try
				{
					isSelfChange = true;
					ListViewHitTestInfo lvhti = listView.HitTest(listView.PointToClient(ListView.MousePosition));

					ListViewItem lvi = lvhti.Item;

					if (!isSelectionContiguous)
						return;

					List<int> indices = new List<int>();
					foreach (int i in listView.SelectedIndices)
						indices.Add(i);
					indices.Sort();

					bool failed = false;
					int lastIdx = -1;
					foreach (int idx in indices)
					{
						if (lastIdx == -1 || idx == lastIdx + 1)
							lastIdx = idx;
						else if (idx != lastIdx + 1)
						{
							failed = true;
							break;
						}
					}

					if (failed)
					{
						listView.SelectedItems.Clear();
						if (lvi != null)
							lvi.Selected = true;
					}
				}
				finally
				{
					if (AfterMultiSelection != null)
						AfterMultiSelection(listView, new EventArgs());

					isSelfChange = false;
				}
		}

		private bool isSelectionContiguous;

		public bool IsSelectionContiguous
		{
			get { return isSelectionContiguous; }
			set { isSelectionContiguous = value; }
		}


	}
}
